import { Action, configureStore } from '@reduxjs/toolkit';
import { ToolkitStore } from '@reduxjs/toolkit/dist/configureStore';
import { AppStore } from '../types';
import detailReducer, { detailEffect } from './detailReducer';
import listReducer, { listEffect } from './listReducer';
import { logoutEffect } from './logoutReducer';
import paginateReducer, { paginateEffect } from './paginateReducer';
import startupReducer, { startUp, startUpEffect } from './startupReducer';
import userReducer, { userEffect } from './userReducer';

// 所有的Effect放到这里
const effectData: { [x: string]: Function } = Object.assign(
  {},
  startUpEffect,
  userEffect,
  logoutEffect,
  listEffect,
  paginateEffect,
  detailEffect,
  {}
);

// 数据中间件 这里综合了所有Effect 已配置到store里 所以store里不需要再动了
const dataMiddleWare = (storeApi: ToolkitStore) => (next: Function) => (action: Action) => {
  next(action);
  let fn = effectData[action.type];
  if (fn) {
    fn(storeApi, action);
  }
};

// 清除数据中间件 清除所有用户相关数据 用于注销
const logoutMiddleware: any = (storeApi: ToolkitStore) => (next: Function) => (action: Action) => {
  next(action);
  // clear
  if (action.type === 'logout/logoutRequest') {
    for (let keys of Object.keys(effectData)) {
      if (keys.includes('/clear')) {
        effectData[keys](storeApi);
      }
    }
  }
};

// 打印中间件 输出store日志
const printMiddleware: any = (storeApi: ToolkitStore) => (next: Function) => (action: Action) => {
  next(action);
  if (process.env.NODE_ENV === 'development') {
    let type: string = action.type.toString().toLowerCase();
    let color = type.includes('failure') ? '#F53F3F' : type.includes('success') ? '#00B42A' : '#3491FA';
    console.log(
      `%c ACTION_TYPE %c ${action.type}`,
      `background:${color};color:white;padding:2px 5px;border:1px solid ${color}; border-radius:3px 0 0 3px;`,
      `background:${color}44;color:${color};padding:2px 5px; border:1px solid ${color}; border-radius:0 3px 3px 0;`
    );
    console.log({ action, store: storeApi.getState() });
  }
};
const store: ToolkitStore<AppStore> = configureStore({
  reducer: {
    startup: startupReducer,
    user: userReducer,
    list: listReducer,
    paginate: paginateReducer,
    detail: detailReducer,
  },
  middleware: [dataMiddleWare, logoutMiddleware, printMiddleware],
});

export default store;

store.dispatch(startUp('start'));
